/*
 * @(#)DocumentContextMenuTag.java
 *
 * Copyright (c) 2004 DCIVision Ltd
 * All rights reserved.
 *
 * This software is the confidential and proprietary information of DCIVision
 * Ltd ("Confidential Information").  You shall not disclose such Confidential
 * Information and shall use it only in accordance with the terms of the license
 * agreement you entered into with DCIVision Ltd.
 */
package com.dcivision.dms.taglib;

import java.sql.Connection;
import java.sql.Timestamp;

import javax.servlet.jsp.JspException;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.struts.taglib.logic.IterateTag;
import org.apache.struts.util.ResponseUtils;

import com.dcivision.dms.DmsOperationConstant;
import com.dcivision.dms.bean.DmsCheckoutHistory;
import com.dcivision.dms.bean.DmsDocument;
import com.dcivision.dms.bean.DmsRoot;
import com.dcivision.dms.bean.DmsVersion;
import com.dcivision.dms.core.DocumentRetrievalManager;
import com.dcivision.dms.core.DocumentValidateManager;
import com.dcivision.dms.core.VersionControlManager;
import com.dcivision.framework.ApplicationException;
import com.dcivision.framework.GlobalConstant;
import com.dcivision.framework.PermissionManager;
import com.dcivision.framework.SessionContainer;
import com.dcivision.framework.SystemFunctionConstant;
import com.dcivision.framework.TextUtility;
import com.dcivision.framework.Utility;
import com.dcivision.framework.taglib.TagUtil;
import com.dcivision.framework.taglib.html.ImgTag;
import com.dcivision.framework.web.WebUtil;

/**
 * Taglib to render the context menu of ParaDOC DmsDocument
 * 
 * @author  Lun Au
 * @company DCIVision Limited
 * @date    2007-05-06
 * @version $Revision: 1.1.2.18 $
 */
public class DocumentContextMenuTag extends ImgTag {
  
  protected Log log = LogFactory.getLog(this.getClass());
  
  public final static String DMS_CONTEXT_MENU_IMAGE = "IconPopupMenu.gif";
  public final static String DMS_CONTEXT_MENU_DISABLED_IMAGE = "IconPopupMenuDisable.gif";

  protected SessionContainer sessionContainer = null;
  protected Connection conn = null;
  protected String contextPath = null;
  protected String imageBase = null;
  
  protected DmsDocument dmsDocument = null;
  protected String sCurFunctionCode = null;
  protected String permissionString = null;
  
  private PermissionManager permissionManager = null;
  private VersionControlManager verControlManager = null;
  private DocumentRetrievalManager docRetrievalManager = null;
  private DocumentValidateManager docValidateManager = null;
  
  public int doEndTag() throws JspException {
    ResponseUtils.write(pageContext, renderContextMenu());
    return SKIP_BODY;
  }

  public int doStartTag() throws JspException {
    dmsDocument = (DmsDocument)pageContext.getAttribute(DmsOperationConstant.DMS_DOCUMENT_BEAN);
    this.init();
    return EVAL_BODY_BUFFERED;
  }

  public String renderContextMenu() {
    StringBuffer sb = new StringBuffer();
    String docItemStatus = dmsDocument.getItemStatus();
    try {
      if (!DmsVersion.ARCHIVED_STATUS.equals(docItemStatus) && GlobalConstant.RECORD_STATUS_ACTIVE.equals(dmsDocument.getRecordStatus())) {
        verControlManager = new VersionControlManager(sessionContainer, conn);
        DmsCheckoutHistory checkoutHistory = verControlManager.getCheckoutHistory(dmsDocument.getCheckoutID());
        Integer checkoutPersonID = new Integer(0);
        String pageURL = null;
        String updateAlertSystemLogID = null;
        String returnTop = null;
        String selfCheckout = null;
        String parentDocType = null;
        
        String rootType = DmsRoot.PUBLIC_ROOT;
        Integer targetID = null;
        String targetItemStatus = null; // Add "targetItemStatus" to handle shortcut target archived problem; lee update for bug 6001/5924
        String targetType="";
        String targetPermissionString = "";
        String targetParentDocType = "";
        String targetRootType = "";
        Integer targetLockUserID = new Integer(0);

        if(DmsVersion.EXCLUSIVE_LOCK.equals(docItemStatus)){
          checkoutHistory = verControlManager.getCheckoutHistory(dmsDocument.getCheckoutID());
          checkoutPersonID = checkoutHistory.getCheckoutPersonID();
        }
        DmsDocument documentRoot = docRetrievalManager.getRootFolderByRootID(dmsDocument.getRootID());
        DmsDocument documentParent = docRetrievalManager.getDocument(dmsDocument.getParentID());
        if( ! Utility.isEmpty(documentParent)) {
          parentDocType = documentParent.getDocumentType();
        }
        if (documentRoot != null){
          if (DmsOperationConstant.DMS_PERSONAL_ROOT.equals(documentRoot.getDocumentName()) && sessionContainer.getUserRecordID().equals(documentRoot.getOwnerID())) {
            permissionString = "PERSONAL";
            sCurFunctionCode = SystemFunctionConstant.DMS_PERSONAL_FOLDER;
          } else {
            // Bill add for EIP-2028
            permissionString = permissionManager.filterDocumentPermissionByWorkflow(conn, GlobalConstant.OBJECT_TYPE_DOCUMENT,dmsDocument.getID());
            sCurFunctionCode = SystemFunctionConstant.DMS_PUBLIC_FOLDER;
          }
          if(DmsDocument.DOCUMENT_LINK.equals(dmsDocument.getDocumentType())){
            DmsDocument newDocument=docRetrievalManager.getRelationshipTargetDocument(dmsDocument.getID(),DmsDocument.DOCUMENT_LINK);
            if (newDocument!=null){
              targetID = newDocument.getID();
              targetItemStatus = newDocument.getItemStatus();
              targetType=newDocument.getDocumentType();
              targetPermissionString = permissionManager.getDocumentLinkPermission(conn, newDocument.getID());
              if( isDocumentExpired(newDocument )) {
                if( sessionContainer.getUserRecordID().equals(newDocument.getOwnerID()) ) {
                  String tmp= "";
                  tmp += targetPermissionString.indexOf("E") != -1 ? "E" : "";
                  tmp += targetPermissionString.indexOf("R") != -1 ? "R" : "";
                  tmp += targetPermissionString.indexOf("D") != -1 ? "D" : "";
                  tmp += targetPermissionString.indexOf("B") != -1 ? "B" : "";
                  targetPermissionString = tmp;
                } else {
                  targetPermissionString = "";
                }
              }
              DmsDocument targetParentDocument = docRetrievalManager.getDocumentByID(newDocument.getParentID());

              DmsDocument targetDocumentRoot = docRetrievalManager.getRootFolderByRootID(newDocument.getRootID());
              
              if (DmsOperationConstant.DMS_PERSONAL_ROOT.equals(targetDocumentRoot.getDocumentName())) {
                targetRootType = DmsRoot.PERSONAL_ROOT;
              } else {
                targetRootType = DmsRoot.PUBLIC_ROOT;
              }
              
              checkoutHistory = verControlManager.getCheckoutHistory(newDocument.getCheckoutID());
              if (!Utility.isEmpty(checkoutHistory)) {
                targetLockUserID = checkoutHistory.getCheckoutPersonID();
              }
              
              if (!Utility.isEmpty(targetParentDocument)){
                targetParentDocType = targetParentDocument.getDocumentType();
              }
              if (DmsOperationConstant.DMS_PERSONAL_ROOT.equals(documentRoot.getDocumentName())) {
                permissionString = "PERSONAL";
                sCurFunctionCode = SystemFunctionConstant.DMS_PERSONAL_FOLDER;
              } else {
                sCurFunctionCode = SystemFunctionConstant.DMS_PUBLIC_FOLDER;
              }
            }
          }
        }
        
        if("PERSONAL".equals(permissionString)){
          rootType=DmsRoot.PERSONAL_ROOT;
        }else{
          rootType=DmsRoot.PUBLIC_ROOT;
        }
        
        if( !"PERSIONAL".equals(permissionString )) {
          if( isDocumentExpired(dmsDocument) ) {
            if( sessionContainer.getUserRecordID().equals(dmsDocument.getOwnerID()) ) {
              String tmp= "";
              tmp += permissionString.indexOf("E") != -1 ? "E" : "";
              tmp += permissionString.indexOf("R") != -1 ? "R" : "";
              tmp += permissionString.indexOf("D") != -1 ? "D" : "";
              tmp += permissionString.indexOf("B") != -1 ? "B" : "";
              permissionString = tmp;
            } else {
              permissionString = "";
            }
          }
        }

        Integer listLoopCnt = (Integer)pageContext.getAttribute("listLoopCnt");
        
        sb.append("<a href=\"javascript:void(0);\" ");
        sb.append("   onclick=\"return getDocumentContextMenu(getMenuText(");
        sb.append("         '"+TextUtility.escapeJSString(getContextMenuTitle()).replaceAll("\'","&acute;")+"', ");
        sb.append("         '"+dmsDocument.getDocumentType()+"', ");
        sb.append("         '"+dmsDocument.getID()+"', ");
        sb.append("         '"+dmsDocument.getParentID()+"', ");
        sb.append("         '"+dmsDocument.getRootID()+"', ");
        IterateTag iterateTag = (IterateTag)findAncestorWithClass(this, IterateTag.class);
        if(iterateTag!=null){
          sb.append("         '"+iterateTag.getIndex()+"', ");
        }else{
          sb.append("         '0', ");  
        }
        sb.append("         '"+docValidateManager.checkExpireDocumentOwner(dmsDocument)+"', ");
        sb.append("         '"+checkoutPersonID+"', ");
        sb.append("         '"+sessionContainer.getUserRecordID()+"', ");
        sb.append("         '"+permissionString+"', ");
        sb.append("         '"+dmsDocument.getHasRelationship()+"', ");
        sb.append("         '" + TextUtility.noNull(pageURL) + "', ");
        sb.append("         '"+rootType+"', ");
        sb.append("         '"+targetType+"', ");
        sb.append("         '"+updateAlertSystemLogID+"', ");
        sb.append("         '"+returnTop+"', ");
        sb.append("         '"+selfCheckout+"', ");
        sb.append("         '"+parentDocType+"', ");
        sb.append("         '"+targetItemStatus+"', ");
        sb.append("         '"+targetPermissionString+"', ");
        sb.append("         '"+targetID+"', ");
        sb.append("         '"+targetParentDocType+"', ");
        sb.append("         '"+targetRootType+"', ");
        sb.append("         '"+targetLockUserID+"', ");
        sb.append("         '"+listLoopCnt+"', ");
        sb.append("         '"+isDocumentExpired(dmsDocument)+"', ");
        sb.append("         '"+isNotYetEffective(dmsDocument)+"' ");
        sb.append("       ));\">");
        sb.append(renderImage(DMS_CONTEXT_MENU_IMAGE));
        sb.append("</a>");
      }else{
        sb.append(renderImage(DMS_CONTEXT_MENU_DISABLED_IMAGE));
      }
    } catch (Exception ex) {
      log.error(ex.getMessage(), ex);
    }
    
    return sb.toString();
  }
  
  private boolean isDocumentExpired(DmsDocument document) {
    Timestamp nowTime = Utility.getCurrentTimestamp();
    Timestamp oneDayBeforeCurrTime = Utility.addDay(nowTime, -1);
    boolean isExpired = true;
    if (document.getEffectiveStartDate()==null && document.getEffectiveEndDate()==null) {
      isExpired=false;
    }
    if (isExpired && (document.getEffectiveStartDate()==null || document.getEffectiveStartDate().equals(nowTime) || document.getEffectiveStartDate().before(nowTime))
         && (document.getEffectiveEndDate()==null || document.getEffectiveEndDate().equals(nowTime) || document.getEffectiveEndDate().after(oneDayBeforeCurrTime))) {
      isExpired=false;
    }
    return isExpired;
  }
  
  protected boolean isNotYetEffective(DmsDocument document) {
    if (document.getEffectiveStartDate() == null) {
      return false;
    }
    
    boolean isNotYetEffective = false;
    
    if (document.getEffectiveStartDate().getTime() >= Utility.getCurrentTimestamp().getTime()) {
      isNotYetEffective = true;
    }
    
    return isNotYetEffective;
  }
  
  protected String getContextMenuTitle() {
    String targetType = "";
    try {
      if(DmsDocument.DOCUMENT_LINK.equals(dmsDocument.getDocumentType())){
        DmsDocument newDocument;
          newDocument = docRetrievalManager.getRelationshipTargetDocument(dmsDocument.getID(),DmsDocument.DOCUMENT_LINK);
        if (newDocument!=null){
          targetType = newDocument.getDocumentType();
        }
      }
      if (DmsDocument.FOLDER_TYPE.equals(dmsDocument.getDocumentType()) || (DmsDocument.DOCUMENT_LINK.equals(dmsDocument.getDocumentType()) && DmsDocument.FOLDER_TYPE.equals(targetType))) {
        return WebUtil.maxString(dmsDocument.getDocumentName(), WebUtil.MAX_LENGTH_OF_FOLDER_CONTEXT_MENU_TITLE);
      }
    } catch (Exception ex) {
      log.error(ex.getMessage(), ex);
    }
    return WebUtil.maxString(dmsDocument.getDocumentName(), WebUtil.MAX_LENGTH_OF_FILE_CONTEXT_MENU_TITLE);
  }
  
  private String nullOrValue(Object obj){
    if(obj == null){
      return null;
    }else{
      return "'"+obj.toString()+"'";
    }
  }
  
  public String renderImage(String image) throws JspException{
    ImgTag imgTag = new ImgTag();
    imgTag.setCommon(true);
    imgTag.setCustomize(false);
    imgTag.setSrc(image);
    String imageHTML = TagUtil.renderTag(pageContext, imgTag);
    return (imageHTML);
  }
  
  protected void init() {
    sessionContainer = (SessionContainer)this.pageContext.getSession().getAttribute(GlobalConstant.SESSION_CONTAINER_KEY);
    conn = (Connection) pageContext.getRequest().getAttribute(GlobalConstant.DB_KEY);
    contextPath = (String)this.pageContext.getServletContext().getAttribute(GlobalConstant.CONTEXT_PATH_KEY);

    sCurFunctionCode = (String)pageContext.getRequest().getAttribute(GlobalConstant.FUNCTION_CODE_KEY); 
    
    permissionManager = sessionContainer.getPermissionManager();
    docRetrievalManager = new DocumentRetrievalManager(sessionContainer, conn);
    verControlManager = new VersionControlManager(sessionContainer, conn);
    docValidateManager = new DocumentValidateManager(sessionContainer, conn);
    DmsDocument documentRoot = null; 

    try {
      documentRoot = docRetrievalManager.getRootFolderByRootID(dmsDocument.getRootID());
      if (documentRoot!=null) {
        if (DmsOperationConstant.DMS_PERSONAL_ROOT.equals(documentRoot.getDocumentName())) {
          permissionString = "PERSONAL";
          sCurFunctionCode = SystemFunctionConstant.DMS_PERSONAL_FOLDER;
        } else {
          //Bill add for EIP-2028
          permissionString = permissionManager.filterDocumentPermissionByWorkflow(conn, GlobalConstant.OBJECT_TYPE_DOCUMENT,dmsDocument.getID());
          sCurFunctionCode = SystemFunctionConstant.DMS_PUBLIC_FOLDER;
        }
      }
    }catch(ApplicationException ae){
      log.error(ae.getMessage(), ae);
    }
    super.init();
  }
  
  public void release(){
    super.release();
    permissionString = null;
    sCurFunctionCode = null;
  }

  public void setDmsDocument(DmsDocument dmsDocument) {
    this.dmsDocument = dmsDocument;
  }
}
